/******************************************************************************
 Copyright (c) 2024-2025 Qualcomm Technologies International, Ltd.
 All Rights Reserved.
 Qualcomm Technologies International, Ltd. Confidential and Proprietary.

******************************************************************************/

#ifndef GATT_RAS_SERVER_PRIVATE_H
#define GATT_RAS_SERVER_PRIVATE_H

#include "csr_bt_usr_config.h"
#include "csr_bt_config.h"

#ifdef INSTALL_CHANNEL_SOUNDING_SUPPORT

#include "csr_bt_gatt_lib.h"
#include "csr_bt_core_stack_pmalloc.h"
#include "csr_bt_gatt_prim.h"
#include "gatt_ras_server.h"
#ifdef CSR_TARGET_PRODUCT_VM
#include "gatt_ras_server_db.h"
#else /* !CSR_TARGET_PRODUCT_VM */
#include "gatt_leaudio_server_db.h"
#endif /* CSR_TARGET_PRODUCT_VM */

/* default client config 0xFFFF means remote client has not written
 * any CCCD which is as good as CCCD disable */
#define GATT_RAS_SERVER_INVALID_CLIENT_CONFIG   0xFFFF

/* Macros for creating messages */
#define MAKE_RAS_SERVER_MESSAGE(TYPE) TYPE##_T* message = (TYPE##_T *)CsrPmemAlloc(sizeof(TYPE##_T))

#define GATT_RAS_SERVER_CCC_NONE                     (0x00)
#define GATT_RAS_SERVER_CCC_NOTIFY                   (0x01)
#define GATT_RAS_SERVER_CCC_INDICATE                 (0x02)

#define GATT_RAS_CLIENT_CONFIG_MASK (GATT_RAS_SERVER_CCC_NOTIFY | GATT_RAS_SERVER_CCC_INDICATE)
#define GET_RAS_CLIENT_CONFIG(config)          (config & GATT_RAS_CLIENT_CONFIG_MASK )

/* Size in octets */
#define GATT_RAS_SERVER_CCC_VALUE_SIZE              (2)
#define GATT_RAS_SERVER_RANGING_DATA_VALUE_SIZE     (2)
#define GATT_RAS_FEATURES_VALUE_SIZE                (4)
#define GATT_RAS_CP_RANGING_DATA_GET_ACK_SIZE       (3)
#define GATT_RAS_CP_ABORT_REQ_SIZE                  (1)
#define GATT_RAS_CP_RLRDS_SIZE                      (5)
#define GATT_RAS_CP_FILTER_RANGING_DATA_SIZE        (3)

#define GATT_RAS_CP_CRDR_SIZE              (3)
#define GATT_RAS_CP_CLRDSR_SIZE            (5)
#define GATT_RAS_CP_RC_SIZE                (2)

/* RAS Response OpCode defines */
#define GATT_RAS_CMPLT_RANGING_DATA_RESPONSE               (0x00)
#define GATT_RAS_CMPLT_LOST_RANGING_DATA_SEG_RESPONSE      (0x01)
#define GATT_RAS_RESPONSE_CODE                             (0x02)

/* RAS operator defines */
#define GATT_RAS_SERVER_OPERATOR_NULL                       (0x00)
#define GATT_RAS_SERVER_OPERATOR_ONE_RANGING                (0x02)
#define GATT_RAS_SERVER_OPERATOR_GREATER_THAN_OR_EQUAL_TO   (0x03)

#define GATT_RAS_SERVER_INVALID_ZERO_CID   (0x00)
#define GATT_RAS_SERVER_INVALID_CID_INDEX  (0xFF)

#define GATT_RAS_SERVER_NUM_OF_MODES       4
#define DEFAULT_FILTER_VALUE_OFF           0xFFFF

#define ANTENNA_PATH_1    (1 << 0)
#define ANTENNA_PATH_2    (1 << 1)
#define ANTENNA_PATH_3    (1 << 2)
#define ANTENNA_PATH_4    (1 << 3)

#define RANGING_HEADER_START_OFFSET 0

#define RAS_MODE0 0
#define RAS_MODE1 1
#define RAS_MODE2 2
#define RAS_MODE3 3

#define RAS_VALUE_SIZE_1OCTET       1
#define RAS_VALUE_SIZE_2OCTET       2
#define RAS_VALUE_SIZE_4OCTET       4

/* These values are Core Spec defined values
 * it should be present in dm_prim.h
 * Remove from here once it is present in
 * dm_prim.h
 */
#define MODE0_PACKET_QUALITY_BIT           0
#define MODE0_PACKET_RSSI_BIT              1
#define MODE0_PACKET_ANTENNA_BIT           2
#define MODE0_MEASURED_FREQ_OFFSET_BIT     3

#define MODE1_PACKET_QUALITY_BIT           0
#define MODE1_PACKET_NADM_BIT              1
#define MODE1_PACKET_RSSI_BIT              2
#define MODE1_TOD_TOA_BIT                  3
#define MODE1_PACKET_ANTENNA_BIT           4
#define MODE1_PACKET_PCT1_BIT              5
#define MODE1_PACKET_PCT2_BIT              6

#define MODE1_TOD_TOA_BIT                  3
#define MODE1_PACKET_PCT1_BIT              5
#define MODE1_PACKET_PCT2_BIT              6

#define MODE2_ANTENNA_PERMUTATION_INDEX_BIT  0
#define MODE2_TONE_PCT_BIT                   1
#define MODE2_TONE_QUALITY_INDICATOR_BIT     2
#define MODE2_TONE_ANTENNA_PATH_1_BIT        3
#define MODE2_TONE_ANTENNA_PATH_2_BIT        4
#define MODE2_TONE_ANTENNA_PATH_3_BIT        5
#define MODE2_TONE_ANTENNA_PATH_4_BIT        6

#define MODE3_PACKET_QUALITY_BIT             0
#define MODE3_PACKET_NADM_BIT                1
#define MODE3_PACKET_RSSI_BIT                2
#define MODE3_TOD_TOA_BIT                    3
#define MODE3_PACKET_ANTENNA_BIT             4
#define MODE3_PACKET_PCT1_BIT                5
#define MODE3_PACKET_PCT2_BIT                6
#define MODE3_ANTENNA_PERMUTATION_INDEX_BIT  7
#define MODE3_TONE_PCT_BIT                   8
#define MODE3_TONE_QUALITY_INDICATOR_BIT     9
#define MODE3_TONE_ANTENNA_PATH_1_BIT       10
#define MODE3_TONE_ANTENNA_PATH_2_BIT       11
#define MODE3_TONE_ANTENNA_PATH_3_BIT       12
#define MODE3_TONE_ANTENNA_PATH_4_BIT       13

#define MODE2_ANTENNA_PERMUTATION_OFFSET    0
#define MODE3_ANTENNA_PERMUTATION_OFFSET    14

#define TONE_ABSENT_IN_EXTENSION_SLOT     0x10
#define TONE_PRESENT_IN_EXTENSION_SLOT    0x20

/* CS Specification for Procedure Done Status */
#define ALL_RESULTS_COMPLETE_FOR_CS_PROCEDURE             0x0
#define PARTIAL_RESULTS_MORE_TO_FOLLOW_FOR_CS_PROCEDURE   0x1
#define ALL_SUBSEQUENT_CS_PROCEDURES_ABORTED              0xF

/* CS Specification for Subevent Done Status */
#define ALL_RESULTS_COMPLETE_FOR_CS_SUBEVENT              0x0
#define PARTIAL_RESULTS_MORE_TO_FOLLOW_FOR_CS_SUBEVENT    0x1
#define CURRENT_CS_SUBEVENT_ABORTED                       0xF

#define SUCCESS (0 << 7)
#define ABORTED (1 << 7)

#define FIRST_SEGMENT_TRUE  1
#define FIRST_SEGMENT_FALSE 0

#define LAST_SEGMENT_TRUE  (1 << 1)
#define LAST_SEGMENT_FALSE (0 << 1)

#define ROLLING_COUNTER_MAX   64

#define END_SEGMENT_MAX       0xFF

#define RAS_DEFAULT_MTU        23

/* Opcode values for the RAS Control Point Characteristic */
typedef enum
{
    GATT_RAS_SERVER_GET_RANGING_DATA            = 0x00,
    GATT_RAS_SERVER_ACK_RANGING_DATA            = 0x01,
    GATT_RAS_SERVER_RETRIEVE_LOST_RANGING_DATA_SEGMENTS   = 0x02,
    GATT_RAS_SERVER_ABORT_OPERATION             =0x03,
    GATT_RAS_SERVER_FILTER_RANGING_DATA         =0x04
} gattRasServerOpCode;

/* Response codes are in accordance with RAS Spec for Response Op Code =0x02 */
typedef enum
{
    GATT_RAS_RESPONSE_CODE_SUCCESS                               = 0x01,
    GATT_RAS_RESPONSE_CODE_UNSUPPORTED_OPCODE                    = 0x02,
    GATT_RAS_RESPONSE_CODE_INVALID_PARAMETER                     = 0x03,
    GATT_RAS_RESPONSE_CODE_FILTER_SETTING_PERSISTED              = 0x04,
    GATT_RAS_RESPONSE_CODE_ABORT_UNSUCCESSFUL                    = 0x05,
    GATT_RAS_RESPONSE_CODE_PROCEDURE_NOT_COMPLETED               = 0x06,
    GATT_RAS_RESPONSE_CODE_SERVER_BUSY                           = 0x07,
    GATT_RAS_RESPONSE_CODE_NO_RECORD_FOUND                       = 0x08
} gattRasServerResponseCode;

typedef struct ras_ranging_data_list
{
   struct ras_ranging_data_list    *next;
   uint8                           *data;
   uint16                          dataLen;
   uint8                           rollingCounter;
   bool                            consumed : 1;
   bool                            partial : 1;
   bool                            transmitted : 1;
} ras_ranging_data_list;


typedef struct
{
    ConnectionIdType             cid;
    uint8                        numOfSegments;
    ras_ranging_data_list        *rangingDataList;
    uint16                       filterMask[GATT_RAS_SERVER_NUM_OF_MODES];
    uint16                       curRangingCounter; /* Current ranging counter procedure data available*/
    uint16                       lastRangingCounterOverwritten; /* Last ranging counter value which was flushed */
    GattRasServerConfigType      clientCfg;
    uint32                       rollingCounter; /* Bit1-6 for 0-63 rolling segment counter */
    uint16                       mtu; /* segments are created based on this value */
    uint8                        selectedTxPower;
    uint8                        subeventDoneStatusOffset;
    uint8                        numOfStepsOffset;
    bool                         procedureActive : 1;
    bool                         rangingDataRequested : 1;
    bool                         triggerCsProcedureComplete : 1;
    bool                         allSegmentsSent : 1; /* All segment for the current procedure is send */
} ras_client_data;

/*! @brief Definition of data required for association.
 */
typedef struct
{
    uint32               rasFeaturesMask;
    ras_client_data      connectedClients[GATT_RAS_MAX_CONNECTIONS];
} ras_data;

/*! @brief The RAS server internal structure for the server role.

    This structure is NOT visible to the application
*/
typedef struct _gatt_ras_server_t
{
    AppTaskData libTask;
    AppTask appTask;

    CsrBtGattId  gattId;    /*! Registered GATT ID */

    /* Service handle provided by the service_handle lib when the server
     * memory instance is created
     */
    RasServiceHandleType srvcHndl;
    uint16 startHandle;
    uint16 endHandle;

    /*! Information to be provided in service characteristics. */
    ras_data data;
} GRASS_T;

#define MAKE_RAS_MESSAGE(TYPE) \
    TYPE * message = (TYPE *)CsrPmemZalloc(sizeof(TYPE))

#define RasServerMessageSend(_appTask, _msg) \
                      CsrSchedMessagePut(_appTask, GATT_RAS_SERVER_PRIM, ((void *)_msg))

#endif /* INSTALL_CHANNEL_SOUNDING_SUPPORT */

#endif /* GATT_RAS_SERVER_PRIVATE_H */